﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using CustomTypes.Interfaces;
//using Microsoft.VisualStudio.Modeling;

namespace devtm.AutoMapper
{
    
    public abstract class TypeRepository
    {


        public EventHandler<AssemblyResolveEventArgs> AssemblyResolver;

        protected Dictionary<string, IAssemblyDescriptor> _dic = new Dictionary<string, IAssemblyDescriptor>();

        public TypeRepository()
        {
            
        }

        public TypeDescriptor GetType(string assemblyName, string @namespace, string name)
        {

            string _assemblyName = assemblyName.Split(',')[0];


            if (_dic.ContainsKey(_assemblyName))
            {
                var ass = _dic[_assemblyName];
                return ass.GetType(@namespace, name);
            }
            else
            {

                IAssemblyDescriptor ass = ResolveAssembly(_assemblyName);
                if (ass != null)                
                    return ass.GetType(@namespace, name);
                
            }

            return null;

        }

        public IEnumerable<TypeDescriptor> GetTypes(string assemblyName, HashSet<string> namespaces)
        {

            string _assemblyName = assemblyName.Split(',')[0];

            if (_dic.ContainsKey(_assemblyName))
            {

                var ass = _dic[_assemblyName];

                foreach (var item in ass.GetTypes(namespaces))
                    yield return item;

            }
            else
            {

                IAssemblyDescriptor ass = ResolveAssembly(_assemblyName);
                if (ass != null)
                    foreach (var item in ass.GetTypes(namespaces))
                        yield return item;

            }

        }

        public IEnumerable<TypeDescriptor> GetTypes(string assemblyName)
        {

            string _assemblyName = assemblyName.Split(',')[0];

            if (_dic.ContainsKey(_assemblyName))
            {

                var ass = _dic[_assemblyName];

                foreach (var item in ass.GetTypes(null))
                    yield return item;

            }
            else
            {

                IAssemblyDescriptor ass = ResolveAssembly(_assemblyName);
                if (ass != null)
                    foreach (var item in ass.GetTypes(null))
                        yield return item;

            }

            
        }
    
        public IEnumerable<TypeDescriptor> GetTypes()
        {

            foreach (var item in _dic)            
                foreach (var type in item.Value.GetTypes(null))
                    yield return type;
            
        }

        public bool Contains(string assemblyName)
        {
            string _assemblyName = assemblyName.Split(',')[0];
            return _dic.ContainsKey(_assemblyName);
        }


    
        public abstract IAssemblyDescriptor ResolveAssembly(string assemblyName);


    }
}
